import React from 'react'
import { createRoot } from 'react-dom/client'
import {
  observable,
  action,
  computed,
  autorun,
  configure,
  runInAction,
} from 'mobx'
import { observer } from 'mobx-react'

import Appp from './App'

// 强制对数据的修改通过被 action 修饰的方法进行
configure({ enforceActions: 'observed' })
// #1 初始化 Mobx 容器
class Store {
  @observable count = 0
  @observable price = 5
  @action.bound increment() {
    this.count++
  }
  // 计算属性
  @computed get totalPrice() {
    return this.price * this.count
  }
  // 建议把数据的修改放到方法里面
  @action.bound change() {
    this.count = 8
    this.count = 9
  }
  @action.bound asyncChange() {
    setTimeout(() => {
      // this.count = 888
      // this.changeCount()
      // 临时定义一个函数并立即执行
      /* action('xxx', () => {
        this.count = 888
      })() */
      runInAction(() => {
        this.count = 888
      })
    }, 1000)
  }
}
// #2 在组件中使用 Mobx 容器状态
// @observer
// class App extends React.Component {
//   render() {
//     const { store } = this.props
//     return (
//       <div>
//         <h3>{store.count}</h3>
//         <p>{store.totalPrice}</p>
//         <button onClick={store.increment}>Increment</button>
//       </div>
//     )
//   }
// }

const store = new Store()

// #3 在组件中发起 action 修改容器状态
createRoot(document.getElementById('root')).render(<Appp />)

autorun(() => {
  console.log('~', store.count, store.price)
})

/* store.count = 8
store.price = 9
// store.change()
const change = store.change
change() */
// 有时候不想定义函数，可以用下面方法来执行对数据的修改
/* runInAction(() => {
  store.count = 10
  store.price = 20
}) */

// 严格模式会报错
store.asyncChange()
